<?php
//
// +------------------------------------------------------------------------+
// | Gecko Framework                                                        |
// +------------------------------------------------------------------------+
//
require_once("Gecko/Form/Exception.php");
require_once("Gecko/Form/Field.php");

/**
 * Select control with a dependant child (AJAX auto fill)
 *
 * @package Gecko.Form.Field;
 * @author Christopher Valderrama <valderrama.christopher@gmail.com>
 * @copyright Copyright (c) 2008
 * @version $Id$v1.0$ 2008
 * @access public
 **/
class Gecko_Form_Field_SelectDependant extends Gecko_Form_Field_Select {
	/**
	 * Control Javascript code to provide ajax
	 * selection
	 *
	 * @var string
	 */
	private $code;

	/**
	 * The MS to run between requests (static shared)
	 * default is 1 sec after page load
	 *
	 * @var int
	 */
	private static $msToRun = 1000;

	/**
	 * The MS to increase between requests
	 *
	 * @var int
	 */
	private $msIncrease = 500;

	/**
	 * Creates a new instance of the Dependant Select Control
	 *
	 * @param string $name
	 * @param string $value
	 * @param array $settings
	 */
	public function __construct($name, $value = "", $settings = array()) {
		parent::__construct($name, $value, $settings);

		$request = new Gecko_Request();
		$process = $request->ajaxControlProcess;
		if( ( $process == "1" ) && ( $name == $request->childControl ) ) {
			echo $this->ajaxProcess($request->parentValue);
			exit();
		}
	}

	/**
	 * Sets the MS to increase between requests
	 *
	 * @param int $ms
	 */
	public function setIncreaseMS($ms) {
		$this->msIncrease = $ms;
	}

	/**
	 * Process a AJAX Request for pull down menu
	 *
	 * @param string $value The Parent control value
	 * @return string
	 */
	public function ajaxProcess($value) {
		$source = $this->source;

		$source->setValue( $value );
		$this->bind();
		$data = $this->controlData;
		$buffer = array();

		foreach( $data as $key => $value ) {
			$buffer[] = $key . "~" . $value;
		}

		return implode( "|", $buffer );
	}

	/**
	 * Returns the JavaScript code of the control
	 *
	 * @return string
	 */
	public function getJavascriptCode() {
		return $this->code;
	}

	/**
	 * Returns the HTML control
	 *
	 * @return string
	 */
	public function getControl() {
		$params = $this->getParams();
		$value = $this->getValue();
		$name = $this->getName();
		$vars = array();

		Gecko_Template::useHelper( "prototype.js" );
		Gecko_Template::useHelper( "GeckoDependantSelects.js" );
		$template = Gecko_Router::LIBRARY_DIR . "/Assets/Form/Templates/SelectDependant.php";

		$onLoadTemplate = "window.setTimeout(function() { %s }, %s);\n";
		$onLoadCode = "";
		if( $value && ( trim( $value ) != trim( $params['emptyLabel'] ) ) ) {
			$ms = self::$msToRun;
			self::$msToRun += $this->msIncrease;
			$onLoadCode .= sprintf( $onLoadTemplate, "dependantSelect_" . $name . ".selectValue($value);", $ms );
		}

		if( $params['childControl'] != null ) {
			$child = $params['childControl'];
			$code = "var dependantSelect_" . $name . " = new GeckoDependantSelects( '$name', '$child' );\n";
			$ms = self::$msToRun;
			self::$msToRun += $this->msIncrease;
			$onLoadCode .= sprintf( $onLoadTemplate, "dependantSelect_" . $name . ".updateChild();", $ms );
		} else {
			$code = "var dependantSelect_" . $name . " = new GeckoDependantSelects( '$name', '' );\n";
		}

		if( !empty( $onLoadCode ) ) {
			$code .= "Event.observe(window, 'load', function() { $onLoadCode });\n";
		}

		$code = Gecko_Template::getJavaScriptTag( $code );
		$this->code = $code;

		$vars['data'] = $this->controlData;
		$vars['name'] = $name;
		$vars['selected'] = $value;
		$vars['emptyLabel'] = $params['emptyLabel'];
		$vars['spinnerDir'] = Gecko_Router::ASSETS_DIR . "/images/spinner.gif";
		$vars['rawName'] = $name;

		$html = Gecko_Template::renderTemplate( $template, $vars, true );
		return $html;
	}
}